
package com.platform.modules.mall.location.hanlder;

import com.alibaba.druid.pool.DruidPooledPreparedStatement;
import com.alibaba.druid.proxy.jdbc.JdbcParameterNull;
import com.alibaba.druid.proxy.jdbc.PreparedStatementProxyImpl;
import com.mysql.cj.jdbc.ClientPreparedStatement;
import lombok.extern.slf4j.Slf4j;
import org.apache.ibatis.logging.jdbc.PreparedStatementLogger;
import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.MappedJdbcTypes;
import org.apache.ibatis.type.MappedTypes;

import java.lang.reflect.Method;
import java.nio.charset.StandardCharsets;
import java.sql.*;

/**
 * sql语句拼接时不带单引号
 *
 * @author Admin
 */
@Slf4j
@MappedJdbcTypes(JdbcType.OTHER)
@MappedTypes({String.class})
public class LocationTypeHanlder extends BaseTypeHandler<String> {

    @Override
    public void setNonNullParameter(PreparedStatement preparedStatement, int i, String payTypeEnum, JdbcType jdbcType) throws SQLException, SQLException {

        System.out.println(preparedStatement.getClass().getName());
        PreparedStatementProxyImpl preparedStatementProxy;
        PreparedStatementLogger preparedStatementLogger = null;
        if(preparedStatement instanceof com.alibaba.druid.pool.DruidPooledPreparedStatement){
            preparedStatementProxy = (PreparedStatementProxyImpl)((DruidPooledPreparedStatement) preparedStatement).getRawStatement();
        }else{
            preparedStatementLogger = (PreparedStatementLogger) java.lang.reflect.Proxy.getInvocationHandler(preparedStatement);
            preparedStatementProxy = ((PreparedStatementProxyImpl) ((DruidPooledPreparedStatement) (preparedStatementLogger).getPreparedStatement()).getRawStatement());
        }

        ClientPreparedStatement statement = (ClientPreparedStatement) preparedStatementProxy.getRawObject();
        if(preparedStatementLogger != null){
            try {
                //通过反射将当前参数添加入日志打印 （去掉当前块不影响使用）s
                Method method = preparedStatementLogger.getClass().getSuperclass().getDeclaredMethod("setColumn", Object.class, Object.class);
                method.setAccessible(true);
                method.invoke(preparedStatementLogger, i, payTypeEnum);
            } catch (Exception e) {
                e.printStackTrace();
//            log.error("sql参数日志打印写入出错！");
            }
        }
        preparedStatementProxy.setParameter(i, JdbcParameterNull.valueOf(Types.OTHER));
        statement.setBytesNoEscapeNoQuotes(i, payTypeEnum.getBytes(StandardCharsets.UTF_8));
    }

    @Override
    public String getNullableResult(ResultSet rs, String columnName) throws SQLException {
        return rs.getString(columnName);
    }

    @Override
    public String getNullableResult(ResultSet rs, int columnIndex) throws SQLException {
        return rs.getString(columnIndex);
    }

    @Override
    public String getNullableResult(CallableStatement cs, int columnIndex) throws SQLException {
        return cs.getString(columnIndex);
    }

}
